/** \file 
 *	\brief 3D data handling.
 */
#ifndef MDS_VECTOR_INCLUDED
#define MDS_VECTOR_INCLUDED 1

#include "../mds/types.h"

/** \brief 3D vector
 
 Must match the size of cl_[float|double]4.
 */
typedef struct
{
	Real x; /*!< X coordinate... */
	Real y; /*!< Y coordinate... */
	Real z; /*!< Z coordinate... */
	union 
	{
		Real          mass;
		Real          inv_mass;
		unsigned char data[sizeof(Real)];
	} info;
	
}
mds_vector;

#define MDS_VECTOR_INIT { 0, 0, 0, {0} }

void mds_vector_cpy( mds_vector *lhs, const mds_vector *rhs ); /*!< lhs  = rhs */
void mds_vector_add( mds_vector *lhs, const mds_vector *rhs ); /*!< lhs += rhs */
void mds_vector_sub( mds_vector *lhs, const mds_vector *rhs ); /*!< lhs -= rhs */
void mds_vector_vec( mds_vector *tgt, const mds_vector *from, const mds_vector *to ); /*!< tgs = to - from */
void mds_vector_ldz( mds_vector *tgt ); /*!< tgt = 0 */
void mds_vector_mul( mds_vector *tgt, const Real u ); /*!< tgt *= u */
void mds_vector_mulset( mds_vector *lhs, const Real u, const mds_vector *rhs ); /*!< lhs = u * rhs */
void mds_vector_muladd( mds_vector *lhs, const Real u, const mds_vector *rhs ); /*!< lhs += u * rhs */
void mds_vector_mulvec( mds_vector *tgt, const Real u, const mds_vector *from, const mds_vector *to); /*!< tgt = u * ( to-from ) */
Real mds_vector_normsq( const mds_vector *tgt ); /*!< |lhs|^2 */
Real mds_vector_length( const mds_vector *tgt ); /*!< |lhs|   */
Real mds_vector_dot( const mds_vector *lhs, const mds_vector *rhs ); /*!< rhs.lhs */

void mds_vector_rand( mds_vector *tgt, const mds_vector *box ); /*!< uniform random in box */
void mds_vector_unit( mds_vector *tgt ); /*!< random unit vector */

int mds_box_parse( mds_vector *box, const char *fmt );


#endif
